/*
 * To change this template, choose Tools | Templates
 * and open the template in the editor.
 */
package wumpus.ambiente;

import wumpus.agente.Agente;

/**
 *
 * @author gregorio
 */
public class Ambiente {

    private static String[][][] ambiente;
    private static final String OURO = "ouro";
    private static final String POCO = "poco";
    private static final String WUMPUS = "wumpus";
    private static final String BRISA = "brisa";
    private static final String FEDOR = "fedor";
    private static final String AVENTUREIRO = "aventureiro";
    private static final String POSICAO_SEGURA = "posicao_segura";
    private static final String FLECHA = "flecha";
    private static final int NUMERO_MAXIMO_DE_LINHAS = 4;
    private static final int NUMERO_MAXIMO_DE_COLUNAS = 4;
    private static final int NUMERO_MAXIMO_TERCEIRA_DIMENSAO = 7;
    private int numeroDePocos = 3;
    private int quantidadeDePoco = 0;
    private int quantidadeDeWumpus = 0;
    private int linha = calculaI();
    private int coluna = calculaJ();

    /**
     * no array conteudoDoArray a posicao:
     * [0] = aventureiro;
     * [1] = ouro;
     * [2] = brisa;
     * [3] = wumpus;
     * [4] = poco;
     * [5] = fedor;
     * [6] = posicao_segura;
     */
    public Ambiente() {
        ambiente = new String[NUMERO_MAXIMO_DE_LINHAS][NUMERO_MAXIMO_DE_COLUNAS][NUMERO_MAXIMO_TERCEIRA_DIMENSAO];
        ambiente[0][0][0] = AVENTUREIRO;
        ambiente[0][0][6] = POSICAO_SEGURA;
    }

    public static String posicaoAtualDoAventureiro(int linha, int coluna) {
        String posicao = String.valueOf(linha) + "," + String.valueOf(coluna);
        return posicao;
    }

    /**
     * metodo que apagara o rastro do aventureiro, sendo que o ag agora ja sabera que a posicao fornecia e segura
     * @param posicaoAtualAgente
     */
    public void atualizaAmbiemte(String posicaoAgente) {
        int linha = Agente.pegaLinha(posicaoAgente);
        int coluna = Agente.pegaColuna(posicaoAgente);
        getAmbiente()[linha][coluna][0] = null;
    }

    /**
     * metodo que ira preencher o ambiente com um wumpus e tres pocos
     */
    public void preencheAmbiente() {
        sorteaPosicao();
        colocaOuro();
        if (quantidadeDePoco < numeroDePocos) {
            colocaPocoNoAmbiente();
        }
        if (quantidadeDeWumpus < 1) {
            colocaWumpusNoAmbiente();
        }
        colocaPosicoesSeguras();
    }

    public void colocaPosicoesSeguras() {
        for (int i = 0; i < ambiente.length; i++) {
            for (int j = 0; j < ambiente.length; j++) {
                for (int z = 0; z < 6; z++) {
                    String s = ambiente[i][j][z];
                    String brisa = ambiente[i][j][2];
                    String wumpus = ambiente[i][j][3];
                    String poco = ambiente[i][j][4];
                    String fedor = ambiente[i][j][5];
                    if (brisa != null || wumpus != null || poco != null || fedor != null) {
                    } else {
                        s = ambiente[i][j][6] = POSICAO_SEGURA;
                    }
                }
            }
        }
    }

    /**
     * metodo que coloca o ouro em uma determinada posicao
     */
    public void colocaOuro() {
        boolean naoTemAventureiro = false;
        String posicaoDoObjeto = getAmbiente()[linha][coluna][0];
        do {
            if (posicaoDoObjeto == null) {
                naoTemAventureiro = true;
                getAmbiente()[linha][coluna][1] = getOURO();
            } else {
                sorteaPosicao();
                posicaoDoObjeto = getAmbiente()[linha][coluna][0];
            }
        } while (!naoTemAventureiro);
    }

    /**
     * metodo que verifica se uma determinada posicao esta ocupada
     * @return true se a posicao estiver ocupada
     */
    public boolean verificaPosicaoOcupada() {
        boolean posicaoOcupada = false;
        if (getAmbiente()[linha][coluna] != null) {
            posicaoOcupada = true;
        }
        return posicaoOcupada;
    }

    /**
     * metodo que coloca os pocos no ambiente, sendo que antes ele verifica
     * se a ultima posicao sorteada nao contem o aventureiro e o ouro
     */
    public void colocaPocoNoAmbiente() {
        String posicaoDoAventureiro = getAmbiente()[linha][coluna][0];
        String posicaoDoOuro = getAmbiente()[linha][coluna][1];
        do {
            if (posicaoDoAventureiro == null & posicaoDoOuro == null) {
                getAmbiente()[linha][coluna][4] = getPOCO();
                quantidadeDePoco++;
                colocaBrisasDoPoco(linha, coluna);
                sorteaPosicao();
                posicaoDoAventureiro = getAmbiente()[linha][coluna][0];
                posicaoDoOuro = getAmbiente()[linha][coluna][1];
            } else {
                //sorteia nova posicao, e vai atualizar as posicoes do aventureiro e do ouro, 
                //para que uma nova verificacao nessas posicoes sejam possiveis
                sorteaPosicao();
                posicaoDoAventureiro = getAmbiente()[linha][coluna][0];
                posicaoDoOuro = getAmbiente()[linha][coluna][1];
            }
        } while (quantidadeDePoco < numeroDePocos);
    }

    /**
     * metodo que ira colocar as brisas do poco
     * @param linha
     * @param coluna
     */
    public void colocaBrisasDoPoco(int linha, int coluna) {
        colocaBrisaEmCima(linha, coluna);
        colocaBrisaEmBaixo(linha, coluna);
        colocaBrisaDireita(linha, coluna);
        colocaBrisaEsquerda(linha, coluna);
    }

    /**
     * metodo que coloca, brisa em uma posicao superior, de um poco, evitando
     * o estouro do array 4 x 4
     * @param linha
     * @param coluna
     */
    public void colocaBrisaEmCima(int linha, int coluna) {
        if (linha < getNUMERO_MAXIMO_DE_LINHAS() - 1) {
            getAmbiente()[linha + 1][coluna][2] = getBRISA();
            getAmbiente()[linha + 1][coluna][6] = null;
        }
    }

    /**
     * metodo que coloca brisa, em uma posicao abaixo, de um poco, evitando
     * o estouro do array 4 x 4
     * @param linha
     * @param coluna
     */
    public void colocaBrisaEmBaixo(int linha, int coluna) {
        if (linha > 0) {
            getAmbiente()[linha - 1][coluna][2] = getBRISA();
            getAmbiente()[linha - 1][coluna][6] = null;
        }
    }

    /**
     * metodo que coloca brisa, em uma posicao a direita, de um poco, evitando
     * o estouro do array 4 x 4
     * @param linha
     * @param coluna
     */
    public void colocaBrisaDireita(int linha, int coluna) {
        if (coluna < getNUMERO_MAXIMO_DE_COLUNAS() - 1) {
            getAmbiente()[linha][coluna + 1][2] = getBRISA();
            getAmbiente()[linha][coluna + 1][6] = null;
        }
    }

    /**
     * metodo que coloca brisa, em uma posicao a esquerda, de um poco, evitando
     * o estouro do array 4 x 4
     * @param linha
     * @param coluna
     */
    public void colocaBrisaEsquerda(int linha, int coluna) {
        if (coluna > 0) {
            getAmbiente()[linha][coluna - 1][2] = getBRISA();
            getAmbiente()[linha][coluna - 1][6] = null;
        }
    }

    /**
     * metodo que coloca o wumpus no ambiente, sendo que ele verifica
     * se a ultima posicao sorteada nao contem um aventureiro
     */
    public void colocaWumpusNoAmbiente() {
        boolean naoTemAventureiro = false;
        String posicaoDoAventureiro = getAmbiente()[linha][coluna][0];
        do {
            do {
                if (posicaoDoAventureiro == null) {
                    naoTemAventureiro = true;
                    getAmbiente()[linha][coluna][3] = getWUMPUS();
                    quantidadeDeWumpus++;
                    colocaFedorNoAmbiente(linha, coluna);
                    sorteaPosicao();
                } else {
                    sorteaPosicao();
                    posicaoDoAventureiro = getAmbiente()[linha][coluna][0];
                }
            } while (!naoTemAventureiro);
        } while (quantidadeDeWumpus < 1);
    }

    /**
     * metodo que ira espalhar o fedor do wumpus
     * @param linha
     * @param coluna
     */
    public void colocaFedorNoAmbiente(int linha, int coluna) {
        colocaFedorEmCima(linha, coluna);
        colocaFedorEmBaixo(linha, coluna);
        colocaFedorDireita(linha, coluna);
        colocaFedorEsquerda(linha, coluna);
    }

    /**
     * metodo que coloca o fedor, em uma posicao superior, do wumpus, evitando
     * o estouro do array 4 x 4
     * @param linha
     * @param coluna
     */
    public void colocaFedorEmCima(int linha, int coluna) {
        if (linha < getNUMERO_MAXIMO_DE_LINHAS() - 1) {
            getAmbiente()[linha + 1][coluna][5] = getFEDOR();
            getAmbiente()[linha + 1][coluna][6] = null;
        }
    }

    /**
     * metodo que coloca o fedor, em uma posicao abaixo, do wumpus, evitando
     * o estouro do array 4 x 4
     * @param linha
     * @param coluna
     */
    public void colocaFedorEmBaixo(int linha, int coluna) {
        if (linha > 0) {
            getAmbiente()[linha - 1][coluna][5] = getFEDOR();
            getAmbiente()[linha - 1][coluna][6] = null;
        }
    }

    /**
     * metodo que coloca brisa, em uma posicao a direita, de um poco, evitando
     * o estouro do array 4 x 4
     * @param linha
     * @param coluna
     */
    public void colocaFedorDireita(int linha, int coluna) {
        if (coluna < getNUMERO_MAXIMO_DE_COLUNAS() - 1) {
            getAmbiente()[linha][coluna + 1][5] = getFEDOR();
            getAmbiente()[linha][coluna + 1][6] = null;
        }
    }

    /**
     * metodo que coloca brisa, em uma posicao a esquerda, de um poco, evitando
     * o estouro do array 4 x 4
     * @param linha
     * @param coluna
     */
    public void colocaFedorEsquerda(int linha, int coluna) {
        if (coluna > 0) {
            getAmbiente()[linha][coluna - 1][5] = getFEDOR();
            getAmbiente()[linha][coluna - 1][6] = null;
        }
    }

    /**
     * metodo que realiza o sorteio das posicoes
     */
    public void sorteaPosicao() {
        linha = calculaI();
        coluna = calculaJ();
    }

    /**
     * metodo que sorteia uma linha da matriz 4 X 4
     * @return
     */
    public int calculaI() {
        int i = (int) (Math.random() * 4);
        return i;
    }

    /**
     * metodo que sorteia uma coluna da matrz 4 X 4
     * @return
     */
    public int calculaJ() {
        int j = (int) (Math.random() * 4);
        return j;
    }

    //############ sets e gets #############    
    public int getQuantidadeDePoco() {
        return quantidadeDePoco;
    }

    public void setQuantidadeDePoco(int quantidadeDePoco) {
        this.quantidadeDePoco = quantidadeDePoco;
    }

    public int getQuantidadeDeWumpus() {
        return quantidadeDeWumpus;
    }

    public void setQuantidadeDeWumpus(int quantidadeDeWumpus) {
        this.quantidadeDeWumpus = quantidadeDeWumpus;
    }

    public void setLinha(int linha) {
        this.linha = linha;
    }

    public int getColuna() {
        return coluna;
    }

    public void setColuna(int coluna) {
        this.coluna = coluna;
    }

    public static String[][][] getAmbiente() {
        return ambiente;
    }

    public static void setAmbiente(String[][][] aAmbiente) {
        ambiente = aAmbiente;
    }

    public static String getOURO() {
        return OURO;
    }

    public static String getPOCO() {
        return POCO;
    }

    public static String getWUMPUS() {
        return WUMPUS;
    }

    public static String getBRISA() {
        return BRISA;
    }

    public static String getFEDOR() {
        return FEDOR;
    }

    public static String getAVENTUREIRO() {
        return AVENTUREIRO;
    }

    public static String getFLECHA() {
        return FLECHA;
    }

    public static int getNUMERO_MAXIMO_DE_LINHAS() {
        return NUMERO_MAXIMO_DE_LINHAS;
    }

    public static int getNUMERO_MAXIMO_DE_COLUNAS() {
        return NUMERO_MAXIMO_DE_COLUNAS;
    }

    public static int getNUMERO_MAXIMO_TERCEIRA_DIMENSAO() {
        return NUMERO_MAXIMO_TERCEIRA_DIMENSAO;
    }

    public static String getPOSICAO_SEGURA() {
        return POSICAO_SEGURA;
    }
}
